﻿// Silver Cow Party POJ - 3268.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//
#define _CRT_SECURE_NO_WARNINGS
#include <iostream>
#include <algorithm>

using namespace std;
//https://vjudge.csgrandeur.cn/problem/POJ-3268


/*
在 N 个农场（1≤N≤1000）中，每个农场有一头奶牛（1≤N≤1000），编号为 1...N，它们将参加在 #X 农场举行的奶牛大派对（1≤X≤N）。
共有 M 条（1≤M≤100,000）单向（单程）道路连接着一对对的农场；道路 i 需要 Ti（1≤Ti≤100）个单位的时间穿过。

每头牛必须步行前往聚会，聚会结束后返回自己的农场。每头牛都是懒惰的，因此会选择时间最短的最佳路线。
由于道路是单向的，一头奶牛的返回路线可能不同于它原先前往聚会的路线。

在所有奶牛中，一头奶牛走到聚会地点再返回所需的时间最长是多少？

输入
第 1 行 三个空格分隔的整数，分别是 N、M 和 X
第 2...M+1 行： 第 i+1 行：用三个空格分隔的整数描述道路 i： Ai、Bi 和 Ti。
描述的道路从 Ai 农场到 Bi 农场，需要 Ti 个时间单位。
输出
第 1 行： 一个整数：任意一头奶牛可能行走的最长时间。

样本
4 8 2
1 2 4
1 3 2
1 4 7
2 1 1
2 3 5
3 1 2
3 4 4
4 2 3

10
提示
奶牛 4 号直接前往聚会地点（3 个单位），然后通过农场 1 号和农场 3 号返回（7 个单位），总共 10 个时间单位。
*/

//floyd tle  进行两次最短路 一次正 一次反 todo

//const int N = 1010;
//int d[N][N];
//int n, m, x;
//
//
//void floyd() {
//	for (int k = 1; k <= n; k++) {
//		for (int i = 1; i <= n; i++) {
//			for (int j = 1; j <= n; j++) {
//				d[i][j] = min(d[i][j], d[i][k] + d[k][j]);
//			}
//		}
//	}
//}
//
//int main()
//{
//	//cin >> n >> m >> x;
//	scanf("%d%d%d",&n,&m,&x);
//	for (int i = 0; i <= n; i++) {
//		for (int j = 0; j <= n; j++) {
//			if (i == j) d[i][j] = 0;
//			else d[i][j] = 0x3f3f3f3f;
//		}
//	}
//
//	for (int i = 0; i < m; i++) {
//		int a, b, t; 
//		//cin >> a >> b >> t;
//		scanf("%d%d%d",&a,&b,&t);
//		d[a][b] = min(t,d[a][b]);
//	}
//
//	floyd();
//
//	int ans = 0;
//	for (int i = 1; i <= n; i++) {
//		for (int j = 1; j <= n; j++) {
//			ans = max(ans, d[i][j] + d[j][i]);
//		}
//	}
//	printf("%d\n",ans);
//	//cout << ans << endl;
//
//	return 0;
//}
// 



const int N = 1010;
int g[N][N];  // 存储每条边
int dist[N];  // 存储1号点到每个点的最短距离
bool st[N];   // 存储每个点的最短路是否已经确定

int n, m, x;

// 求1号点到n号点的最短路，如果不存在则返回-1
int dijkstra()
{
    memset(dist, 0x3f, sizeof dist);
    memset(st, 0, sizeof st);
    dist[x] = 0;

    for (int i = 0; i < n - 1; i++)
    {
        int t = -1;     // 在还未确定最短路的点中，寻找距离最小的点
        for (int j = 1; j <= n; j++)
            if (!st[j] && (t == -1 || dist[t] > dist[j]))
                t = j;

        // 用t更新其他点的距离
        for (int j = 1; j <= n; j++)
            dist[j] = min(dist[j], dist[t] + g[t][j]);

        st[t] = true;
    }

    if (dist[n] == 0x3f3f3f3f) return -1;
    return dist[n];
}


int main() {
    cin >> n >> m >> x;
    for (int i = 0; i <= n; i++) {
        for (int j = 0; j <= n; j++) {
            if (i == j)g[i][j] = 0;
            else g[i][j] = 0x3f3f3f3f;
        }
    }
    for (int i = 0; i < m; i++) {
        int a, b, w; cin >> a >> b >> w;
        g[a][b] = min(g[a][b], w);
    }

    dijkstra();
    int distback[N];
    memcpy(distback,dist, sizeof dist);

    for (int i = 0; i <= n; i++) {
        for (int j = i; j <= n; j++) {
            swap(g[i][j], g[j][i]);
        }
    }

    dijkstra();
    int ans = 0;
    for (int i = 1; i <= n; i++) {
        ans = max(ans, dist[i] + distback[i]);
    }
    cout << ans << endl;

    return 0;
}